package com.zmn.oms.services.impl.changerecord;

import com.alibaba.fastjson.JSON;
import com.zmn.common.utils.collection.CollectionUtil;
import com.zmn.common.utils.number.NumberUtil;
import com.zmn.oms.manager.utils.MongodbConsts;
import com.zmn.oms.model.dto.changerecord.ChangeServiceItemDTO;
import com.zmn.oms.model.entity.log.OrderLog;
import com.zmn.oms.model.entity.product.OrderProduct;
import com.zmn.oms.model.entity.serviceitem.OrderServiceItem;
import com.zmn.oms.model.entity.work.OrderWork;
import com.zmn.oms.services.interfaces.changerecord.OrderServiceItemChangeRecordService;
import com.zmn.oms.services.interfaces.product.OrderProductService;
import com.zmn.oms.services.interfaces.serviceitem.OrderServiceItemService;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Sort;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.stereotype.Service;

import java.util.List;
import java.util.Objects;
import java.util.Optional;

/**
 * 描述：
 *
 * @author xiewenbing
 * @since 2022/5/24 23:15
 */
@Slf4j
@Service("orderServiceItemChangeRecordService")
public class OrderServiceItemChangeRecordServiceImpl implements OrderServiceItemChangeRecordService {

    @Autowired
    private OrderProductService orderProductService;

    @Autowired
    private OrderServiceItemService orderServiceItemService;

    @Autowired
    MongoTemplate mongoTemplate;

    /**
     * 保存修改
     * @param orderLog
     * @param dbOrderWork
     * @param newOrderWork
     */
    @Override
    public void updateOrderServiceItemChange(OrderLog orderLog, OrderWork dbOrderWork, OrderWork newOrderWork, boolean forcedUpdate) {

        // 参数判断
        if (Objects.isNull(orderLog) || Objects.isNull(dbOrderWork)) {
            return;
        }

        log.info("#orderServiceItemChangeRecordService#updateOrderServiceItemChange,[{}][{}][{}][{}]",dbOrderWork.getOrderId(),
                dbOrderWork.getWorkId(), orderLog.getType(), orderLog.getTypeName());

        // 判断是否修改
        if (!forcedUpdate && !this.isChanged(dbOrderWork,newOrderWork)) {
            return;
        }

        // 构造保存数据
        ChangeServiceItemDTO changeServiceItemDTO = new ChangeServiceItemDTO();
        changeServiceItemDTO.setOrderId(dbOrderWork.getOrderId());
        changeServiceItemDTO.setWorkId(dbOrderWork.getWorkId());
        changeServiceItemDTO.setOperatorId(orderLog.getOperatorId());
        changeServiceItemDTO.setOperator(orderLog.getOperator());
        changeServiceItemDTO.setOperateTime(orderLog.getCreateTime());

        // 产品信息
        changeServiceItemDTO.setProductId(dbOrderWork.getProductId());
        List<OrderProduct> orderProducts = orderProductService.listOrderProductByOrderId(dbOrderWork.getOrderId());
        if (CollectionUtil.isNotNullOrEmpty(orderProducts)) {
            changeServiceItemDTO.setProductName(orderProducts.get(0).getProductName());
        }

        // 服务项信息
        List<OrderServiceItem> orderServiceItemList = orderServiceItemService.listByOrderId(dbOrderWork.getOrderId());
        changeServiceItemDTO.setServcieItemList(orderServiceItemList);

        // 价格信息
        Integer totalAmount = Optional.ofNullable(newOrderWork).map(o->o.getOriginalAmount()).orElse(0);
        if (NumberUtil.isNullOrZero(totalAmount) && CollectionUtil.isNotNullOrEmpty(orderServiceItemList)) {
            totalAmount = orderServiceItemList.stream().filter(item->NumberUtil.isNotNullOrZero(item.getTotalPrice())).
                    mapToInt(item->item.getTotalPrice()).sum();
        }
        changeServiceItemDTO.setTotalAmount(totalAmount);

        // 保存到mongo
        this.saveToMongo(changeServiceItemDTO);
    }

    /**
     * 判断是否修改
     * @param dbOrderWork
     * @param orderWork
     * @return
     */
    private boolean isChanged(OrderWork dbOrderWork, OrderWork orderWork) {

        if (Objects.isNull(orderWork)) {
            return true;
        }

        // 产品ID是否变更
        boolean changed = !Objects.equals(dbOrderWork.getProductId(), orderWork.getProductId()) ||
                !Objects.equals(dbOrderWork.getShowProductId(), orderWork.getShowProductId());
        if (changed) {
            return true;
        }

        // 渠道变化
        changed = !NumberUtil.isNullOrZero(orderWork.getChannelId()) && !Objects.equals(orderWork.getChannelId(), dbOrderWork.getChannelId());;
        if (changed) {
            return true;
        }

        // 城市变化
        changed = !NumberUtil.isNullOrZero(orderWork.getCityId()) && !Objects.equals(orderWork.getCityId(), dbOrderWork.getCityId());
        if (changed) {
            return true;
        }

        // 价格变化
        changed = !NumberUtil.isNullOrZero(orderWork.getOriginalAmount()) && !Objects.equals(orderWork.getOriginalAmount(), dbOrderWork.getOriginalAmount());
        if (changed) {
            return true;
        }

        return false;
    }

    /**
     * 将数据保存到Mongo
     * @param changeServiceItemDTO
     */
    private void saveToMongo(ChangeServiceItemDTO changeServiceItemDTO) {

        if (Objects.isNull(changeServiceItemDTO)) {
            return;
        }

        log.info("#orderServiceItemChangeRecordService#saveToMongo [{}]", JSON.toJSONString(changeServiceItemDTO));

        // 保存逻辑 - 赵宗春
        // 设计两次存储：最后一次变更、倒数第二次变更
        //1、当第一次变更服务项，则：最后一次变更：存储第一次变更数据、倒数第二次变更为：空
        //2、当第二次变更服务项，则：最后一次变更：第二次变更数据、倒数第二次变更为：第一次变更数据
        //3、当第三次变更服务项，则：最后一次变更：第三次变更数据、倒数第二次变更为：第二次变更数据
        Query query = new Query();
        Criteria criteria = new Criteria();
        criteria.and("workId").is(changeServiceItemDTO.getWorkId());
        criteria.and("orderId").is(changeServiceItemDTO.getOrderId());
        query.addCriteria(criteria);
        query.with(Sort.by(Sort.Order.desc("sort")));

        List<ChangeServiceItemDTO> changeServiceItemDTOList = mongoTemplate.find(query, ChangeServiceItemDTO.class,
                MongodbConsts.OMS_ORDER_CHANGE_SERVICE_ITEM_RECORD);

        // 没有则直接保存
        if (CollectionUtil.isNullOrEmpty(changeServiceItemDTOList)) {
            changeServiceItemDTO.setSort(0);
            mongoTemplate.save(changeServiceItemDTO, MongodbConsts.OMS_ORDER_CHANGE_SERVICE_ITEM_RECORD);
            return;
        }

        changeServiceItemDTO.setSort(1);

        // 有1个保存
        if (changeServiceItemDTOList.size() <= 1L) {
            changeServiceItemDTO.setSort(1);
            mongoTemplate.save(changeServiceItemDTO, MongodbConsts.OMS_ORDER_CHANGE_SERVICE_ITEM_RECORD);
            return;
        }

        ChangeServiceItemDTO changeServiceItemDTOFirst = changeServiceItemDTOList.get(0);
        changeServiceItemDTOFirst.setSort(0);

        // 删除所有
        mongoTemplate.remove(query, ChangeServiceItemDTO.class, MongodbConsts.OMS_ORDER_CHANGE_SERVICE_ITEM_RECORD);

        // 重新保存
        mongoTemplate.save(changeServiceItemDTOFirst, MongodbConsts.OMS_ORDER_CHANGE_SERVICE_ITEM_RECORD);
        mongoTemplate.save(changeServiceItemDTO, MongodbConsts.OMS_ORDER_CHANGE_SERVICE_ITEM_RECORD);
    }
}
